#import "MapSearchListViewer.h"

// Singleton instance of MapSearchListViewer
static MapSearchListViewer* sharedMapSearchListViewer = nil;

/**
 * A MapSearchListViewer is an object representing the view that 
 * displays a list of search options for the map.
 *
 * A MapBuildingSearchDelegate must be set to respond to events from
 * within the inner map building search viewer.
 *
 * A SFUEventSearchResponseDelegate must be set to respond to events
 * from within the event search viewer.
 *
 * @author      James Lin
 * @version     0.8.6
 * @since       0.8.6
 * @see         MapBuildingSearchDelegate
 * @see         SFUEventSearchResponseDelegate
 */
@implementation MapSearchListViewer

/**
 * Retrieve the shared instance of the map search list viewer.
 *
 * @return  the shared instance of MapSearchListViewer
 */
+ (MapSearchListViewer*)sharedMapSearchListViewer {
	@synchronized(self) {
		if (sharedMapSearchListViewer == nil) {
			sharedMapSearchListViewer = [[MapSearchListViewer alloc] init];
		}
		return sharedMapSearchListViewer;
	}
}

/**
 * Allocate the map search list viewer.
 *
 * @return  the newly allocated shared instance of MapSearchListViewer
 */
+ (id) alloc {
	@synchronized(self) {
		sharedMapSearchListViewer = [super alloc];
		return sharedMapSearchListViewer;
	}
}

/**
 * Retrieve a copy of the map search list viewer.
 *
 * @return  the shared instance of MapSearchListViewer
 */
+ (id) copy {
	@synchronized(self) {
		return sharedMapSearchListViewer;
	}
}

/**
 * Display the listing of search options in a new view.
 *
 * Pushes this view onto the navigation controller stack of the parent
 * view. Upon tapping the back button, the view is automatically 
 * popped off the top of the navigation stack.
 *
 * @param navController  the navigation controller of the parent view
 * @param bDelegate      the delegate handling building search events
 * @param sDelegate      the delegate handling event search events
 */
- (void)displayWithNavController:(UINavigationController*)navController
			  bldgSearchDelegate:(id<MapBuildingSearchDelegate>)bDelegate 
			 eventSearchDelegate:(id<SFUEventSearchResponseDelegate>)eDelegate {
	// Create the table of search options
	searchTableView = [[UITableView alloc] initWithFrame:CGRectMake(0, 0, 
																   VIEW_WIDTH, VIEW_HEIGHT) 
												  style:UITableViewStylePlain];
	searchTableView.backgroundColor = [UIColor lightGrayColor];
	searchTableView.separatorColor = [UIColor whiteColor];
	searchTableView.tableFooterView = [[[UIView alloc] 
									   initWithFrame:CGRectMake(0, 0, 1, 60)] autorelease];

	self.navigationItem.title = @"Search";
	[searchTableView setRowHeight:BUILDING_CELL_HEIGHT*2];
	[searchTableView setDelegate:self];
	[searchTableView setDataSource:self];
	parentNav = navController;
	
	bSearchDelegate = bDelegate;
	eSearchDelegate = eDelegate;
	
	searchOptionsList = [[SFUConstants getSearchOptions] retain];
	[searchTableView reloadData];
	
	// Display the table of search options
	[self.view addSubview:searchTableView];
	[parentNav pushViewController:self animated:YES];
}

/**
 * Handle a building search request.
 *
 * Passes the delegate responder chain back to caller of this view.
 *
 * @param building  the building of which a search is requested
 */
- (void)searchRequestByBuilding:(Building*)building isNew:(BOOL) isNew{
	[bSearchDelegate searchRequestByBuilding:building isNew:YES];
	[parentNav popViewControllerAnimated:NO];
}

/**
 * Get the number of rows in the table view.
 */
- (NSInteger)tableView:(UITableView*)tableView numberOfRowsInSection:(NSInteger)section {
	return searchOptionsList.count;
}

/**
 * Populate a table view cell in the table view with content.
 */
- (UITableViewCell*)tableView:(UITableView*)tableView 
		cellForRowAtIndexPath:(NSIndexPath*)indexPath {
	static NSString* CellIdentifier = @"SearchOptionCell";
	UITableViewCell* cell = [searchTableView dequeueReusableCellWithIdentifier:CellIdentifier];
	
	if (cell == nil) {
		// Create an empty reusable cell for performance sake
		cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault 
									   reuseIdentifier:CellIdentifier] autorelease];
		
		// Set the background color for the cell when selected
		UIView* cellView = [[[UIView alloc] init] autorelease];
		cellView.backgroundColor = [UIColor darkGrayColor];
		cell.selectedBackgroundView = cellView;
	}
	
	cell.textLabel.text = [searchOptionsList objectAtIndex:indexPath.row];
	cell.textLabel.font = [UIFont boldSystemFontOfSize:16.0];

	return cell;
}

/**
 * Display the view of the search option selected.
 */
- (void)tableView:(UITableView*)tableView didSelectRowAtIndexPath:(NSIndexPath*)indexPath {
	[tableView deselectRowAtIndexPath:indexPath animated:YES];
	switch (indexPath.row) {
		case 0:
		{
			BuildingCollection* bc = [BuildingCollection sharedBuildingCollection];
			MapBuildingSearchView* mbsv = [MapBuildingSearchView sharedMapBuildingSearchView];
			[mbsv setDelegate:self];
			[mbsv displayViewWithBuildings:[bc getSortedBuildings] 
							 navController:self.navigationController];
			break;
		}
		case 1:
		{
			MapSearchUtility* msu = [MapSearchUtility sharedMapSearchUtility];
			[msu setDelegate:eSearchDelegate];
			[msu searchEventsWithNavController:self.navigationController 
								searchDelegate:self];
			break;
		}
	}
}

/**
 * Receives the set of event matches generated by an event search
 * 
 * @param eventMatches  array of matching events
 */
- (void)eventResponseBySearchSuccess:(NSArray*)eventMatches {
	[eSearchDelegate eventResponseBySearchSuccess:eventMatches];
	[parentNav popViewControllerAnimated:NO];
}

/**
 * Receives the set of event matches generated by an event search
 * 
 * @param msg  reason for failure
 */
- (void)eventResponseBySearchFailure:(NSString*)msg {
	UIAlertView* alertView = [[[UIAlertView alloc] initWithTitle:msg 
														 message:@"" 
														delegate:self 
											   cancelButtonTitle:@"Ok" 
											   otherButtonTitles:nil] autorelease];
	[alertView show];
	[parentNav popViewControllerAnimated:NO];
}

/**
 * Deallocate the map search list viewer
 */
- (void)dealloc {
	[searchOptionsList release];
	searchOptionsList = nil;
	[searchTableView release];
	searchTableView = nil;
	[sharedMapSearchListViewer release];
	sharedMapSearchListViewer = nil;
    [super dealloc];
}

@end
